package com.boil.util;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.serializer.SerializerFeature;
import com.alibaba.fastjson.serializer.ValueFilter;
import org.apache.commons.lang3.StringUtils;

import java.util.*;

/**
 * Created by ChenYong on 2016-09-21.
 * <br>
 * Fast Json 工具类。
 */
public final class FastJsonUtils {
    /**
     * 将 Json 字符串转换为 Json 实例。
     *
     * @param json Json 字符串
     * @return Json 实例
     */
    public static JSONObject json2JSONObject(String json) {
        if (StringUtils.isBlank(json)) {
            return null;
        }

        return JSON.parseObject(json);
    }

    /**
     * 将实例转换为 Json 字符串。
     *
     * @param bean 实例
     * @return Json 字符串
     */
    public static String bean2Json(Object bean) {
        if (bean == null) {
            return "";
        }

        return JSON.toJSONString(bean, //
                valueFilter, // 值过滤器
                SerializerFeature.QuoteFieldNames, // 输出 key 时使用双引号
                SerializerFeature.WriteMapNullValue, // 输出值为 null 的字段
                SerializerFeature.WriteNullListAsEmpty, // List 字段如果为 null，输出为 []，而非 null
                SerializerFeature.WriteNullNumberAsZero, // 数值字段如果为 null，输出为 0，而非 null
                SerializerFeature.WriteNullStringAsEmpty, // 字符类型字段如果为 null，输出为 ""，而非 null
                SerializerFeature.WriteNullBooleanAsFalse); // Boolean 字段如果为 null，输出为 false，而非 null
    }

    /**
     * 将 Json 字符串转换为实例。
     *
     * @param json  Json 字符串
     * @param clazz 实例的类类型
     * @return 实例
     */
    public static <T> T json2Bean(String json, Class<T> clazz) {
        if (StringUtils.isBlank(json) || (clazz == null)) {
            return null;
        }

        return JSON.parseObject(json, clazz);
    }

    /**
     * 将 Json 字符串转换为 <code>List</code>。
     *
     * @param json  Json 字符串
     * @param clazz 实例的类类型
     * @return <code>List</code>
     */
    public static <T> List<T> json2List(String json, Class<T> clazz) {
        if (StringUtils.isBlank(json) || (clazz == null)) {
            return new ArrayList<T>();
        }

        return JSON.parseArray(json, clazz);
    }

    /**
     * 将 Json 字符串转换为 <code>Set</code>。
     *
     * @param json  Json 字符串
     * @param clazz 实例的类类型
     * @return <code>Set</code>
     */
    public static <T> Set<T> json2Set(String json, Class<T> clazz) {
        return new HashSet<T>(json2List(json, clazz));
    }

    /**
     * 将 Json 字符串转换为 <code>Map</code>。
     *
     * @param json   Json 字符串
     * @param kClazz 键的类类型
     * @param vClazz 值的类类型
     * @return <code>Map</code>
     */
    public static <K, V> Map<K, V> json2Map(String json, Class<K> kClazz, Class<V> vClazz) {
        if (StringUtils.isBlank(json) ||//
                (kClazz == null) || //
                (vClazz == null)) {
            return new HashMap<K, V>();
        }

        return (Map<K, V>) JSON.parse(json);
    }

    /**
     * 值过滤器。
     */
    private static ValueFilter valueFilter = new ValueFilter() {
        @Override
        public Object process(Object object, String name, Object value) {
            if (value == null) {
                return "";
            }

            return value;
        }
    };
}